import React, {
	useMemo,
	useCallback,
	useImperativeHandle,
	forwardRef,
} from "react";
import { Transforms, createEditor } from "slate";
import { withHistory } from "slate-history";
import {
	Slate,
	Editable,
	withReact,
	useSelected,
	useFocused,
} from "slate-react";

const MentionExample = ({value,setValue}, ref) => {
	const renderElement = useCallback((props) => <Element {...props} />, []);
	const editor = useMemo(
		() => withMentions(withReact(withHistory(createEditor()))),
		[]
	);

	const addNode = useCallback(
		(val, text) => {
			const mention = {
				type: "mention",
				character: val,
				children: [{ text, bold: true }],
			};
			Transforms.insertNodes(editor, mention);
			Transforms.move(editor);
		},
		[editor]
	);
	useImperativeHandle(ref, () => ({
		addNode,
	}));

	return (
		<Slate
			editor={editor}
			initialValue={value}
            value={[]}
			onChange={(val) => {
                setValue(val)
				// console.log("val==", val);
			}}
		>
			<Editable
				renderElement={renderElement}
				// onKeyDown={onKeyDown}
				placeholder="Enter some text..."
			/>
		</Slate>
	);
};

const withMentions = (editor) => {
	const { isInline, isVoid, markableVoid } = editor;

	editor.isInline = (element) => {
		return element.type === "mention" ? true : isInline(element);
	};

	editor.isVoid = (element) => {
		return element.type === "mention" ? true : isVoid(element);
	};

	editor.markableVoid = (element) => {
		return element.type === "mention" || markableVoid(element);
	};

	return editor;
};

const Element = (props) => {
	const { attributes, children, element } = props;
	switch (element.type) {
		case "mention":
			return <Mention {...props} />;
		default:
			return <p {...attributes}>{children}</p>;
	}
};

const Mention = ({ attributes, children, element }) => {
	const selected = useSelected();
	const focused = useFocused();
	const style = {
		padding: "3px 3px 2px",
		margin: "0 1px",
		verticalAlign: "baseline",
		display: "inline-block",
		borderRadius: "4px",
		backgroundColor: "#eee",
		fontSize: "0.9em",
		boxShadow: selected && focused ? "0 0 0 2px #B4D5FF" : "none",
	};
	// See if our empty text child has any styling marks applied and apply those
	if (element.children[0].bold) {
		style.fontWeight = "bold";
	}
	if (element.children[0].italic) {
		style.fontStyle = "italic";
	}
	return (
		<span
			{...attributes}
			contentEditable={false}
			data-cy={`mention-${element.character.replace(" ", "-")}`}
			style={style}
		>
			{element.character}
			{children}
		</span>
	);
};

const initialValue = [
	{
		type: "paragraph",
		children: [
			{
				text: "This example shows how you might implement a simple ",
			},
			{
				text: "@-mentions",
				bold: true,
			},
		],
	},
	{
		type: "paragraph",
		children: [
			{
				type: "mention",
				character: "R2-D2",
				children: [{ text: "", bold: true }],
			},
			{ text: " or " },
			{
				type: "mention",
				character: "Mace Windu",
				children: [{ text: "" }],
			},
			{ text: "!" },
		],
	},
];

export default forwardRef(MentionExample);
